package Thread;

import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

/**
 * Created with IntelliJ IDEA.
 * Description:
 * User: homechen
 * Date: 2024-03-16
 * Time: 10:37
 */
public class SolveDeadLockDemo2 {
    private static void pollingLock(Lock lockA, Lock lockB) {
        while (true) {
            if (lockA.tryLock()) {  // 尝试获取锁A
                System.out.println("线程1：获取到锁A！");
                try {
                    Thread.sleep(1000);
                    System.out.println("线程1：等待获取锁B！");
                    if (lockB.tryLock()) {
                        try {
                            System.out.println("线程1：获取到锁B！");
                        } finally {
                            lockB.unlock();
                            System.out.println("线程1：释放锁B！");
                            break;
                        }
                    }
                } catch (InterruptedException e) {
                    e.printStackTrace();
                } finally {
                    lockA.unlock();
                    System.out.println("线程1：释放锁A！");
                }
            }

            // 获取锁A失败  等待 1 秒再获取
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }

    public static void main(String[] args) {
        Lock lockA = new ReentrantLock();
        Lock lockB = new ReentrantLock();

        // 创建线程一（使用轮询锁）
        Thread t1 = new Thread(new Runnable() {
            @Override
            public void run() {
                pollingLock(lockA, lockB);
            }
        });
        t1.start();

        Thread t2 = new Thread(new Runnable() {
            @Override
            public void run() {
                lockB.lock(); // 加锁
                System.out.println("线程2：获取到锁B！");
                try {
                    Thread.sleep(1000);
                    System.out.println("线程2：等待获取锁A！");
                    lockA.lock();
                    try {
                        System.out.println("线程2：获取到锁A！");
                    } finally {
                        lockA.unlock();
                    }
                } catch (InterruptedException e) {
                    e.printStackTrace();
                } finally {
                    lockB.unlock();
                }
            }
        });
        t2.start();
    }
}
